package com.company.sendemo.basics.yaDesignMode.singleton;

//单例模式
//测试单例设计模式--就是按照一定的开发步骤，按照一定的模板进行开发，达到程序汇只会有一个实例在干活的目的！！
public class SingleTon {
    public static void main(String[] args){
        //4,测试 new多少次都是一个对象？？？--
//     MySingleTon m = new MySingleTon();--构造方法私有化
        SingleTon1 m1 = SingleTon1.getMy();
        SingleTon1 m2 = SingleTon1.getMy();
        System.out.println(m1==m2);//是同一个对象吗？？？
        System.out.println(m1.equals(m2));//默认用Object的==

        SingleTon2 s1 = SingleTon2.getMy();
        SingleTon2 s2 = SingleTon2.getMy();
        System.out.println(s1 == s2);
        System.out.println(s1.equals(s2));

        System.out.println(s1.equals(m2));
    }
}
//饿汉式
class SingleTon1{
    //1，私有化构造方法 -- 目的就是控制外界创建对象的权利
    private SingleTon1(){};
    //2封装创建好 的对象  --封装，不让外界随意看到我创建的对象
    //创建静态的全局唯一的对象
    private static SingleTon1 my =  new SingleTon1();
    //3,提供公的获取对象的方法
    //静态方法，因为没法newl，还想用，就用类名访问--修饰成静态的
    public static SingleTon1 getMy(){
        return my;//静态只能调用静态
    }
}

//懒汉式 -- 面试重点！！延迟加载思想+线程不安全
class SingleTon2{
    // 1,私有化改造方法 -- 目的就是控制外界创建对象的权利
    private SingleTon2(){}
    // 2,封装创建好的对象 -- 先不创建对象，啥时候用啥时候创建！！
    ////创建静态的全局唯一的对象
    private static SingleTon2 my;
    // 3,提供公的获取对象的方法
    // 静态方法，因为没法new了，还想用，就用类名访问--修饰成静态的
    synchronized public static SingleTon2 getMy(){//b，方法里都是同步代码，可以是同步方法
//     synchronized (MySingleTon23.class) {//a，同步代码块，静态方法的锁，是类名.class本类的字节码对象
        // t1,t2,t3来准备new
        if (my == null) {
            // t1 new
            // t2 new
            // t3 new
            my = new SingleTon2();// 开始创建！！ 延迟加载
        }
//     }
        return my;// 静态只能调静态
    }
}
